﻿using System;
using System.Collections.Generic;
using System.Text;

namespace Zeo
{
    public class SleepStats
    {
        public enum AlarmReason
        {
            /// <summary>
            /// SmartWake detected REM to non-REM transition and rang alarm.
            /// </summary>
            REM_TO_NON_REM_TRANSITION, 
            /// <summary>
            /// SmartWake detected non-REM to REM transition and rang alarm. 
            /// </summary>
            NON_REM_TO_REM_TRANSITION,
            /// <summary>
            /// SmartWake detected wake and rang alarm.
            /// </summary>
            WAKE,
            /// <summary>
            /// SmartWake detected sleep depth rising and rang alarm.
            /// </summary>
            DEEP_RISING,
            /// <summary>
            /// Set alarm time was reached. SmartWake may or may not be active.
            /// </summary>
            END_OF_WAKE_WINDOW,
            /// <summary>
            /// Alarm did not ring.
            /// </summary>
            NO_ALARM,
        }

        public enum SleepStatsGrouping
        {
            /// <summary>
            /// If using date range: This takes all records within the specified inclusive date range and average them all together to a single averaged result
            /// If using by count: take the number of daily records specified and average them
            /// </summary>
            COMBINED,
            /// <summary>
            /// Stats averaged over each day 
            /// </summary>
            DAILY,
            /// <summary>
            /// Stats averaged over each week 
            /// </summary>
            WEEKLY,
            /// <summary>
            /// Stats averaged over each month 
            /// </summary>
            MONTHLY,
        }

        public enum SleepStage
        {
            /// <summary>
            /// Represents a time block where no data is available.
            /// </summary>          
            UNDEFINED,
            /// <summary>
            /// Represents a time block where the subject was awake.
            /// </summary>
            WAKE,  
            /// <summary>
            /// Represents a time block where the subject was in REM sleep. 
            /// </summary>
            REM,
            /// <summary>
            /// Represents a time block where the subject was in LIGHT sleep. 
            /// </summary>
            LIGHT,
            /// <summary>
            /// Represents a time block where the subject was in DEEP sleep 
            /// </summary>
            DEEP,
        }

        public class SleepStageInfo
        {
            public SleepStageInfo(SleepStage stage)
            {
                this.Stage = stage;
            }

            /// <summary>
            /// The stage of sleep
            /// </summary>
            public SleepStage Stage = SleepStage.UNDEFINED;
            /// <summary>
            /// The amount of time spent in stage
            /// </summary>
            public TimeSpan Time = TimeSpan.Zero;
            /// <summary>
            /// The amount of time spent (in percentage of total) in stage
            /// </summary>
            public double TimePercent = 0;
            /// <summary>
            /// The number of ZQ points accounting for stage
            /// </summary>
            public double ZQPoints = 0;
        }

        /// <summary>
        /// The number of times the individual woke up during the period
        /// </summary>
        public int NumAwakenings = 0;
        /// <summary>
        /// The number of ZQ points due to awakenings
        /// </summary>
        public double AwakeningsZQPoints = 0;
        /// <summary>
        /// A DateTime object describing the bed time
        /// </summary>
        public DateTime BedTime;
        /// <summary>
        /// The SleepStatsGrouping Enum describing the method in which the data was averaged
        /// </summary>
        public SleepStatsGrouping Grouping = SleepStatsGrouping.COMBINED;
        /// <summary>
        /// An integer from 1-5 describing how the user felt that morning (1=bad,5=great!)
        /// </summary>
        public int MorningFeel = 3;
        /// <summary>
        /// A DateTime object describing the rise time
        /// </summary>
        public DateTime RiseTime;
        /// <summary>
        /// A DateTime object describing the start date for the SleepStats object
        /// </summary>
        public DateTime StartDate;
        /// <summary>
        /// Info for the deep sleep stages
        /// </summary>
        public SleepStageInfo DeepStageInfo = new SleepStageInfo(SleepStage.DEEP);
        /// <summary>
        /// Info for the light sleep stages
        /// </summary>
        public SleepStageInfo LightStageInfo = new SleepStageInfo(SleepStage.LIGHT);
        /// <summary>
        /// Info for the REM sleep stages
        /// </summary>
        public SleepStageInfo RemStageInfo = new SleepStageInfo(SleepStage.REM);
        /// <summary>
        /// Info for wake stages
        /// </summary>
        public SleepStageInfo WakeStageInfo = new SleepStageInfo(SleepStage.WAKE);
        /// <summary>
        /// The amount of time it took to fall asleep
        /// </summary>
        public TimeSpan TimeToSleep = TimeSpan.Zero;
        /// <summary>
        /// The total time asleep
        /// </summary>
        public TimeSpan TotalSleep = TimeSpan.Zero;
        /// <summary>
        /// The number of ZQ points accounting for Total Z
        /// </summary>
        public double TotalSleepZQPoints = 0;
        /// <summary>
        /// The overall ZQ score for this sleep period
        /// </summary>
        public double TotalZQScore = 0;
    }
}
